#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <mntent.h>
#include <errno.h>
#include <sys/vfs.h>

#include "socs/usr/sysinfo.h"

struct sysmem *get_sysmem(struct sysmem *mem)
{
	FILE *fd;
	char buf[256];
	struct sysmem *m = mem;
	fd = fopen("/proc/meminfo", "r");

	if (fd == NULL) {
		printf("fopen failded \n");
		return NULL;
	}

	fgets(buf, sizeof(buf), fd);
	sscanf(buf, "%s %lu %s", m->name1, &m->total, m->name2);
	fgets(buf, sizeof(buf), fd);
	sscanf(buf, "%s %lu %s", m->name1, &m->free, m->name2);
	fclose(fd);
	return mem;
}

struct syscpu *get_syscpu(struct syscpu *cpu)
{
	FILE *fd;
	char buf[256];
	fd = fopen ("/proc/stat", "r");

	if (fd == NULL) {
		printf("fopen failded \n");
		return NULL;
	}

	fgets (buf, sizeof(buf), fd);
	sscanf (buf, "%s %u %u %u %u", cpu->name, &cpu->user, &cpu->nice, &cpu->system,
			&cpu->idle);
	fclose(fd);
	return cpu;
}
int cal_syscpu (struct syscpu *o, struct syscpu *n)
{
	unsigned long od, nd;
	unsigned long id, sd, ud;
	int  cpu_use = 0;
	od = (unsigned long) (o->user + o->nice + o->system + o->idle);
	nd = (unsigned long) (n->user + n->nice + n->system + n->idle);
	ud = (unsigned long) (n->user - o->user);
	id = (unsigned long) (n->nice - o->nice);
	sd = (unsigned long) (n->system - o->system);

	if ((nd - od) != 0) {
		cpu_use = (int )((sd + id) * 100) / (nd - od);
	} else {
		cpu_use = 0;
	}

//    printf("cpu: %d\n",cpu_use);
	return cpu_use;
}
struct sysdisk *get_sysdisk(struct sysdisk *disk)
{
	struct statfs	fs_info;
	struct mntent	*mnt_info;
	FILE			*fh;
	float			percent;
	unsigned long	sum_Total = 0, total_free = 0;

	if ((fh = setmntent("/etc/mtab", "r")) == NULL) {
		printf("Cannot open /etc/mtab file!:%s\n", strerror(errno));
		return NULL;
	}

	while ((mnt_info = getmntent(fh)) != NULL) {
		if (statfs(mnt_info->mnt_dir, &fs_info) < 0) {
			continue;
		}

		if (strcmp(mnt_info->mnt_type, "proc") &&
			strcmp(mnt_info->mnt_type, "devfs") &&
			strcmp(mnt_info->mnt_type, "usbfs") &&
			strcmp(mnt_info->mnt_type, "sysfs") &&
			strcmp(mnt_info->mnt_type, "tmpfs") &&
			strcmp(mnt_info->mnt_type, "devpts") &&
			strcmp(mnt_info->mnt_type, "fusectl") &&
			strcmp(mnt_info->mnt_type, "debugfs") &&
			strcmp(mnt_info->mnt_type, "binfmt_misc") &&
			strcmp(mnt_info->mnt_type, "fuse.gvfs_fuse_daemon") &&
			strcmp(mnt_info->mnt_type, "securityfs")) {
			if (fs_info.f_blocks != 0) {
				percent = ((float)fs_info.f_blocks - (float)fs_info.f_bfree * 100.0 /
						   (float)fs_info.f_blocks);
			} else {
				percent = 0;
			}
		} else {
			continue;
		}

		unsigned long block_size = fs_info.f_bsize / 1024;
		sum_Total += fs_info.f_blocks * block_size / 1024;
		total_free += fs_info.f_bavail * block_size / 1024;
	}

	disk->total = sum_Total / 1024;
	disk->free = total_free / 1024;
	return disk;
}
